/**
 * 
 */
package model.session;

import java.util.concurrent.Semaphore;

import controller.IExecutionListener;
import controller.SessionManager;

/**
 * <p>
 * A {@link} SessionBlock} that can be executed in a thread.
 * </p>
 * <p>
 * You have to give it a {@link Semaphore} that will be released by the executable class as soon as
 * it run for sure. It is use for example be sure that a {@link SessionManager} can't be closed
 * before a solver has been completely lunched, in this case the session will be close but the
 * solver will still be running.
 * </p>
 * 
 * @author GRONOWSKI Stephane svan001@aol.com
 * 
 *         igsat 2010
 * 
 */
public abstract class ExecutableSessionBlock extends SessionBlock implements Runnable {


	protected ExecutionStatus		status;
	protected IExecutionListener	listener;
	protected Semaphore				sem			= null;
	protected String				description	= null;

	/**
	 * @return the {@link Semaphore} used by the block.
	 */
	public Semaphore getSem() {
		return sem;
	}

	/**
	 * Set the {@link Semaphore} used by the block
	 * 
	 * @param sem
	 *            the sem to set
	 */
	public void setSem(Semaphore sem) {
		this.sem = sem;
	}

	/**
	 * @return the {@link IExecutionListener} that listen to this block.
	 */
	public IExecutionListener getListener() {
		return listener;
	}

	/**
	 * Set the {@link IExecutionListener} that listen to this block.
	 * 
	 * @param listener
	 *            the listener to set
	 */
	public void setListener(IExecutionListener listener) {
		this.listener = listener;
	}

	/**
	 * @return the {@link ExecutionStatus} of the block.
	 */
	public ExecutionStatus getStatus() {
		return status;
	}

	/**
	 * Set the {@link ExecutionStatus} of the block.
	 * 
	 * @param status
	 *            the status to set
	 */
	public void setStatus(ExecutionStatus status) {
		this.status = status;
	}

	/**
	 * Create a executable session block.
	 * 
	 * @param first
	 *            the first block of the session {@link SessionBlock}
	 * @param status
	 *            the status of the block
	 */
	public ExecutableSessionBlock(SessionBlock first, ExecutionStatus status) {
		super(first);
		this.status = status;
	}

	/**
	 * Return the description of the executable.
	 * 
	 * @return the description of the executable.
	 */
	public String getDescritpion() {
		return description;
	}

	/**
	 * Set the description of the executable.
	 * 
	 * @param descritpion
	 *            the description to set
	 */
	public void setDescritpion(String descritpion) {
		this.description = descritpion;
	}

	@Override
	public abstract void run();

	/**
	 * Stop the current execution.
	 */
	public abstract void stopExecution();

}
